package com.imooc.SmartChargeStation.demo.netty.handlers;

import com.imooc.SmartChargeStation.demo.websocket.spring.handler.ImoocHandler;
import io.netty.buffer.ByteBuf;
import io.netty.channel.*;
import io.netty.handler.codec.mqtt.MqttMessage;
import io.netty.util.ReferenceCountUtil;
import io.netty.util.ReferenceCounted;
import lombok.extern.slf4j.Slf4j;

import java.lang.ref.Reference;
import java.nio.charset.StandardCharsets;

/**
 * author: zpy
 * description: 自定义服务端(入站)处理器
 * date: 2025/8/20
 */

@Slf4j
public class ImoocServerHandler extends SimpleChannelInboundHandler<ByteBuf> {
/*
    怎么理解ImoocServerHandler继承SimpleChannelInboundHandler和ChannelInboundHandlerAdapter的区别？
    将ImoocServerHandler理解成点菜记录员，Simple相当于一张写的神奇纸条，用户点完菜后，纸条会自行销毁；而非Simple
    需要顾客在点完菜后，服务员手动将该纸条扔进垃圾桶。
    也就是：
    a.SimpleChannelInboundHandler提供了泛型, 无需进行类型转换
    b.消息的释放, SimpleChannelInboundHandler自动的释放引用计数对象,而ChannelInboundHandlerAdapter不会自动释放

    此类实现的是继承SimpleChannelInboundHandler
*/
    /**
     * description: 客户端连接成功触发
     * UnderStanding：新客人在指定位置坐下，点菜记录员注意到："3号桌有新客人入座，准备记录点菜"
     */
    @Override
    public void handlerAdded(ChannelHandlerContext ctx) throws Exception {
        log.info(">>>>>SimpleChannelInboundHandler有新的客户端连接："+ctx.channel().id().asLongText());
    }

    /**
     * description: 接收到消息触发
     * UnderStanding：点菜记录员将声音转化成文字
     */
    @Override
    protected void channelRead0(ChannelHandlerContext ctx, ByteBuf msg) throws Exception {
        //顾客给点菜员说的是菜名这个声音，点菜员需要将这个“声音”记录到菜单纸上
        String message = msg.toString(StandardCharsets.UTF_8);
        log.info(">>>>>SimpleChannelInboundHandler收到的消息："+message);

        //将消息传递给下一个处理器
        //ctx.fireChannelRead(msg);

        //msg.release();

/*
    假如采用这个类继承的是ChannelInboundHandlerAdapter，那么还需要进行哪些处理呢？
    1.将消息传递给下一个处理器
    ctx.fireChannelRead(msg);
    2.如果没有将消息传递给下一个处理器，则要在该处理器释放ByteBuf对象
    ReferenceCountUtil.release();直接调用ByteBuf对象的release方法
    msg.release();通过工具类释放引用计数对象
 */
    }
}
